﻿using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Pumpkin.FrameBase;

using MessageID = System.UInt16;

namespace KBEngine
{
    public class Message
    {
        public Int16 msglen = -1;
        private CrossDomainInstance crossMessage;
        public Message(CrossDomainInstance cross)
        {
            crossMessage = cross;
            msglen = (Int16)crossMessage.Invoke("getLen");
        }

        #region CrossMethods
        public void handleMessage(MemoryStream ms)
        {
            crossMessage.Invoke("handleMessage", ms);
        }
        #endregion
    }

    public class Messages
    {
        private static Dictionary<MessageID, Message> clientMessages = new Dictionary<MessageID, Message>();
        private static Dictionary<string, Message> messages = new Dictionary<string, Message>();
        private static Messages instance_;
        private static CrossDomainInstance crossMessages;

        public Messages()
        {
            if (instance_ != null)
            {
                Debug.LogError("Messages must be a single instance");
            }

            instance_ = this;
            crossMessages = CrossInstanceFactory.Instance.CreateWithInstantial(BaseCrossType.Messages);
        }
        public static Message GetClientMessage(MessageID id)
        {
            Message msg = null;
            if (clientMessages.TryGetValue(id, out msg))
            {
                return msg;
            }
            else
            {
                string cls = getClientMessageCls(id);
                cls = HotFixConfigs.CrossNamespacePrefix + cls;
                if(!BaseCrossType.IsClassRegisted(cls))
                {
                    BaseCrossType.RegistMethod(cls, "handleMessage", 1);
                    BaseCrossType.RegistMethod(cls, "getLen", 0);
                }

                var crossMsg = CrossInstanceFactory.Instance.Create(cls);
                object obj = crossMessages.StaticInvoke("getClientMessage", id);
                crossMsg.SetInstance(obj);
                clientMessages[id] = new Message(crossMsg);
                return msg;
            }
        }

        public static Message GetMessages(string name)
        {
            Message msg = null;
            if (messages.TryGetValue(name, out msg))
            {
                return msg;
            }
            else
            {
                string cls = "Message_" + name;
                cls = HotFixConfigs.CrossNamespacePrefix + cls;
                if (!BaseCrossType.IsClassRegisted(cls))
                {
                    BaseCrossType.RegistMethod(cls, "handleMessage", 1);
                    BaseCrossType.RegistMethod(cls, "getLen", 0);
                }

                var crossMsg = CrossInstanceFactory.Instance.Create(cls);
                object obj = crossMessages.StaticInvoke("getMessage", name);
                if (obj == null)
                {
                    Debug.LogError("cant find message "+ name +"in dll");
                }
                msg = new Message(crossMsg);
                messages[name] = msg;
                return msg;
            }
        }

        #region
        public static string getClientMessageCls(MessageID id)
        {
            return (string)crossMessages.StaticInvoke("getClientMessageCls", id);
        }

        public static object getClientMessage(MessageID id)
        {
            return crossMessages.StaticInvoke("getClientMessage", id);
        }
        #endregion
    }
}